package com.kehutong.payfees.service.receipt;

import com.kehutong.common.DeptService;
import com.kehutong.common.DoveClient;
import com.kehutong.common.dto.DeptDTO;
import com.kehutong.common.urlconfig.FileUrlConfig;
import com.kehutong.common.util.Token;
import com.kehutong.payfees.entity.ChargeBill;
import com.kehutong.payfees.entity.ChargeBillItem;
import com.kehutong.payfees.entity.receipt.ReceiptManage;
import com.kehutong.payfees.entity.receipt.ReceiptOrder;
import com.kehutong.payfees.entity.receipt.ReceiptStatistics;
import com.kehutong.payfees.enums.BillPaidState;
import com.kehutong.payfees.util.BasicClient;
import com.kehutong.payfees.util.PdfTableUtil;
import com.kehutong.payfees.util.PdfUtil;
import org.coraframework.converter.util.StringUtil;
import org.coraframework.inject.Inject;
import org.coraframework.json.JSONArray;
import org.coraframework.json.JSONObject;
import org.coraframework.logger.Logger;
import org.coraframework.logger.LoggerFactory;
import org.coraframework.mvc.http.result.Result;
import org.coraframework.orm.Pool;
import org.coraframework.orm.jdbc.JdbcSession;
import org.coraframework.orm.jdbc.Page;
import org.coraframework.orm.jdbc.execute.entity.FindPage;
import org.coraframework.util.Objects;

import java.io.File;
import java.io.FileOutputStream;
import java.util.*;

/**
 * @program: kht
 * @description:
 * @author: joneron
 * @create: 2021/6/2
 **/
public class ReceiptOrderServiceImpl {

    private static final Logger logger = LoggerFactory.getLogger(ReceiptOrderServiceImpl.class);

    @Inject
    private JdbcSession jdbcSession;

    @Inject
    private FileUrlConfig fileUrlConfig;

    @Inject
    private DoveClient doveClient;

    @Inject
    BasicClient basicClient;

    @Inject
    DeptService deptService;

    public Page<ReceiptOrder> findPage(JSONObject jsonObject) {

        FindPage<ReceiptOrder> find = jdbcSession.findPage(ReceiptOrder.class)
                .eq("deleted", false)
                .eq(jsonObject,"status")
                .eq(jsonObject,"communityNo")
                .like(jsonObject,"receiptNo")
                .like(jsonObject,"communityList")
                .like(jsonObject,"createTime")
                .order("createTime", "desc");

        find.page(jsonObject);

        return find.exe();
    }

    public List<ReceiptOrder> findList(JSONObject jsonObject) {

        List<ReceiptOrder> receiptList = jdbcSession.findArray(ReceiptOrder.class)
                .eq("deleted", false)
                .eq("status",true)
                .exe();

        return receiptList;
    }

    /**
     * 生成收据信息
     * @param entity
     * @return
     */
    public Integer save(ReceiptOrder entity) throws Exception {

        return jdbcSession.insert(entity);
    }

    public Integer update(ReceiptOrder entity) {
        return jdbcSession.updateById(entity);
    }

    public Integer deleteById(String id) {
        ReceiptOrder result = Pool.get(ReceiptOrder.class, id);
        if (result != null) {
            result.setDeleted(true);
            jdbcSession.updateById(result);
        }
        return 1;
    }

    /**
     * 手动生成收据
     * @param receiptOrder
     * @return
     * @throws Exception
     */
    public Object savePdf(ChargeBill receiptOrder, String companyNo) throws Exception {

        logger.info("手动生成PDF文件！小区编号：{}",receiptOrder.getCommunityNo());

        ReceiptManage receiptManage;
        try {
            //1、查询电子签章,判断是否有配置收据模板及公章
            receiptManage = jdbcSession.findOne(ReceiptManage.class)
                    .like("communityList", receiptOrder.getCommunityNo())
                    .eq("status", true).exe();

            if (null == receiptManage) {
                logger.error("{}小区未设置收据模板！", receiptOrder.getCommunityNo());
                return Result.error(0, "请先去设置或开启收据模板！");
            }
        }catch (Exception e){
            return Result.error(0, "票据模板设置不合理，同一个小区只能配置一个模板！");
        }

        //2、查询账单缴费状态
        ChargeBill chargeBill = jdbcSession.findById(ChargeBill.class,receiptOrder.getId());

        if(chargeBill.getPaidState().equals(BillPaidState.UNPAID)){
            logger.error("{}未缴费，不能生成收据！",receiptOrder.getCommunityNo());
            return Result.error(0,  "未缴费不能生成收据！");
        }

        //3、查询账单数据
        Map<String,Object> mapParam = new LinkedHashMap<String,Object>();
        mapParam.put("company", receiptManage.getReceiptTitleName());
        mapParam.put("community",chargeBill.getCommunityName());
        String realName; //房屋客人名称
        if(StringUtil.isEmpty(chargeBill.getPayerName())){
            realName =  getOwnerName(companyNo,chargeBill.getHouseNo());
        }else{
            realName = chargeBill.getPayerName();
        }
        //房东姓名
        mapParam.put("realName",realName);
        // 显示： 12栋-1801
        StringBuffer houseInfo = new StringBuffer();
        houseInfo.append(chargeBill.getBuildingName()).append("-");
        if(StringUtil.isNotBlank(chargeBill.getUnitName())){
            houseInfo.append(chargeBill.getUnitName()).append("-");
        }
        houseInfo.append(chargeBill.getHouseName());
        mapParam.put("houseInfo",houseInfo);  //房号
        mapParam.put("datePay",chargeBill.getPaidAt());
        String receiptNo = PdfTableUtil.generateNumber("SJ");
        mapParam.put("receiptNO","NO."+receiptNo);
        //上传的签章图片
        String fileImg = fileUrlConfig.getFile(receiptManage.getSealImgId());
        mapParam.put("sealFile",fileImg);
        mapParam.put("type","receipt");
        mapParam.put("totalAmount",chargeBill.getTotal());
        mapParam.put("content",chargeBill.getBillDateFrom() +"至"+chargeBill.getBillDateTo());
        mapParam.put("payMethod",receiptOrder.getPayMethod().getDesc());

        //查询账单项
        List<ChargeBillItem> billItems = jdbcSession.findArray(ChargeBillItem.class)
                .eq("billNo", chargeBill.getId()).exe();
        mapParam.put("dataList",billItems);

        //4、生成PDF文件
        PdfUtil pdfUtil = new PdfUtil();
        byte[] pdf = pdfUtil.execute(mapParam);

        String pdfName = receiptNo+".pdf";
        File file = new File(pdfName);

        FileOutputStream outputFileStream = new FileOutputStream(file);
        outputFileStream.write(pdf);
        outputFileStream.close();

        //保存收据单数据
        ReceiptOrder receipt =  Pool.newInstance(ReceiptOrder.class);
        receipt.setReceiptNo(receiptNo); //生成自定义编号
        receipt.setPayOrderNo(chargeBill.getId());
        JSONObject jsonObject =  fileUrlConfig.sendFile(file, http->{ });
        String fileId = jsonObject.getJSONObject("data").getString("id");
        receipt.setFileId(fileId);
        receipt.setHouseInfo(houseInfo.toString());
        receipt.setCommunityNo(receiptOrder.getCommunityNo());
        receipt.setCommunityName(receiptOrder.getCommunityName());
        receipt.setBatchPayOrderNo(receiptOrder.getChargeRecordId());
        receipt.setDepartmentNo(receiptOrder.getDepartmentNo());
        receipt.setDepartmentName(receiptOrder.getDepartmentName());
        receipt.setDepartmentNos(receiptOrder.getDepartmentNos());

        jdbcSession.insert(receipt);

        //文件上传成功后自动删除
        if (file.exists() && file.isFile() && file.delete() == true) {
            logger.info("{}本地文件已经删除!",pdfName);
        }

        //代表已经生成过了
        chargeBill.setFileId(fileId);

        return jdbcSession.updateById(chargeBill);
    }

    public String getOwnerName(String companyNo, String houseNo) throws Exception{

        JSONObject result = doveClient.post("/basic/house/service/get", http->{
            http.addHeader("companyNo", companyNo);
            http.addParam("id", houseNo);
        });

        if (Objects.isNull(result) || Objects.isNull(result.getJSONObject("data"))) {
            return "";
        }

        JSONObject data = result.getJSONObject("data");

        return data.getString("ownerName");
    }

    public List<ReceiptStatistics> groupData(JSONObject jsonObject,Token token) throws Exception {

        String date1 = "2021-06-01"; //本月
        String date2 = "2021-05-01"; //上个月
        String strDate = jsonObject.getString("statistTime");
        if(null != strDate){
            date1 = strDate.substring(0,7);
            int num = Integer.parseInt(date1.substring(5,7))-1;
            date2 = date1.substring(0,5) + String.format("%02d", num);
        }else {
            //2.根据小区统计数据
            Calendar cal = Calendar.getInstance();
            int year = cal.get(Calendar.YEAR);
            int monthly = cal.get(Calendar.MONTH) + 1;
            int month = cal.get(Calendar.MONTH);
            //本月 (0 代表前面补充0,10代表长度为10,d 代表参数为正数型)
            date1 = year +"-"+ String.format("%02d", monthly);
            //上一个月 (0 代表前面补充0,10代表长度为10,d 代表参数为正数型)
            date2 = year +"-"+String.format("%02d", month);
        }

        List<ReceiptStatistics> statList = new ArrayList<>();
        String data3 = date1;
        String data4 = date2;

        JSONArray array = jsonObject.getJSONArray("communitys");

        for (int i = 0; i < array.size(); i++) {
            String communityId = array.getString(i);

            List<ReceiptOrder> receiptList1 = jdbcSession.findArray(ReceiptOrder.class)
                    .like("createTime",data3)
                    .eq("communityNo",communityId).exe();

            List<ReceiptOrder> receiptList2 = jdbcSession.findArray(ReceiptOrder.class)
                    .like("createTime",data4)
                    .eq("communityNo",communityId).exe();

            List<ReceiptOrder> receiptListAll = jdbcSession.findArray(ReceiptOrder.class)
                    .eq("communityNo",communityId).exe();

           // String viewName = v.getString("name");

            ReceiptStatistics receipt = new ReceiptStatistics();
            receipt.setCommunityName(communityId);
            receipt.setLastMonthNum(receiptList2.size());
            receipt.setMonthlyNum(receiptList1.size());
            receipt.setTotalNum(receiptListAll.size());

            statList.add(receipt);

        }

/**
        Map<String,JSONObject> communityMap = basicClient.getCommunityMap(token);
        //communityMap.get(data.getString("communityNo")).getString("name"));
        communityMap.forEach((k,v)->{

            List<ReceiptOrder> receiptList1 = jdbcSession.findArray(ReceiptOrder.class)
                    .like("createTime",data3)
                    .eq("communityNo",k).exe();

            List<ReceiptOrder> receiptList2 = jdbcSession.findArray(ReceiptOrder.class)
                    .like("createTime",data4)
                    .eq("communityNo",k).exe();

            List<ReceiptOrder> receiptListAll = jdbcSession.findArray(ReceiptOrder.class)
                    .eq("communityNo",k).exe();

            String viewName = v.getString("name");

            ReceiptStatistics receipt = new ReceiptStatistics();
            receipt.setCommunityName(viewName);
            receipt.setLastMonthNum(receiptList2.size());
            receipt.setMonthlyNum(receiptList1.size());
            receipt.setTotalNum(receiptListAll.size());

            statList.add(receipt);
        });*/

        return statList;
    }

}
